function init() {
    class esp_ws {
        websock = null;
        term = null;
        authStatus = 0;
        fitAddon = null;
        constructor() {
            let div = document.createElement("div");
            div.id = "terminal";
            div.style = "height: 100%; width: 100%; background-color: #000c; color: white; bottom: 0; position: absolute;";
            document.body.appendChild(div);
            this.openShell();
            this.initWebsocket();
        }
        setAuthStatus(state) {
            this.authStatus = state
        }
        getAuthStatus() {
            return this.authStatus;
        }
        initWebsocket() {
            this.term.writeln("正在连接服务器......");
            let hostname = window.location.hostname;
            if (hostname !== '127.0.0.1')
                this.websock = new WebSocket('ws://' + hostname + '/v1/ws');
            else
                this.websock = {};
            this.websock.onmessage = this.websocketonmessage;
            this.websock.onopen = this.websocketonopen;
            this.websock.onerror = this.websocketonerror;
            this.websock.onclose = this.websocketclose;
            this.websock.class = this;
        }
        openShell() {
            const fitAddon = new FitAddon.FitAddon();
            this.fitAddon = fitAddon;
            let term = new Terminal({
                rendererType: 'canvas', //渲染类型
                convertEol: true, //启用时，光标将设置为下一行的开头
                disableStdin: false, //是否应禁用输入。
                cursorStyle: "underline", //光标样式
                cursorBlink: true, //光标闪烁
                theme: {
                    foreground: 'white', //字体
                    background: '#000c', //背景色
                    cursor: 'help', //设置光标
                },
                screenKeys: true,
                useStyle: true,
                fontFamily: `'Fira Mono', monospace`,
                fontSize: 15,
            });
            this.term = term;
            this.term.loadAddon(fitAddon);
            this.term.prompt = () => {
                this.term.write('\r\nTTG@root:/$ ')
            }
            this.term.open(document.getElementById('terminal'));
            document.getElementsByClassName('terminal')[0].style.height = "100%";
            this.term.focus();
            fitAddon.fit();

            this.term.writeln('Welcome to esp_web_shell')
            this.term.writeln('Power By maplerian.')
            this.term.onResize(e => {
                console.log(e);
                fitAddon.fit();
            })
            window.addEventListener("resize", e => {
                console.log(e);
                fitAddon.fit();
            })
            this.term.onData((data) => {
                if (data.charCodeAt() == 127)
                    data = '\b';
                this.websock.send(data);
            });
            this.term.onKey(e => {
                const ev = e.domEvent
                const printable = !ev.altKey && !ev.altGraphKey && !ev.ctrlKey && !ev.metaKey
                if (e.key == '\x16') {
                    console.log("paste")
                    //ctrol+ c copy
                } else if (e.key == '\x03' && term.hasSelection()) {
                    console.log("copy")
                    if (document.execCommand)
                        document.execCommand("copy");
                }
            })

            document.querySelectorAll(".xterm-viewport")[0].style = "background-color: rgb(0 0 0 / 0%);";
        }
        closeShell() {
            if (this.term)
                this.term.dispose();
            this.term = null;
        }
        shell_write(data) {
            if (this.term)
                this.term.write(data);
        }
        websocketonopen(e) {
            console.log("open", e);
        }
        websocketonerror(e) {
            console.log("err", e);
        }
        websocketclose(e) {
            console.log('断开连接', e);
            this.class.term.writeln("连接断开......");
            this.class.initWebsocket();
        }
        websocketonmessage(e) {
            if (e.data.indexOf("{") == 0) {
                const redata = JSON.parse(e.data);
                console.log(redata);
                if (typeof redata.code === 'undefined' && redata.key) {
                    let push_data = {
                        shell: 1,
                    }
                    this.send(JSON.stringify(push_data));

                    if (localStorage.getItem("key")) {
                        push_data = {
                            key: localStorage.getItem("key")
                        }
                        this.send(JSON.stringify(push_data));
                    } else if (storage_key) {
                        let data = JSON.parse(storage_key);
                        if (data.name && data.passwd) {
                            let md5_data = md5(data.name + "|" + data.passwd + "|" + redata.key);
                            push_data = {
                                name: data.name,
                                passwd: md5_data
                            }
                            this.send(JSON.stringify(push_data));
                        }
                    }
                } else if (redata.code == 0) {
                    this.class.term.writeln("连接成功.");
                    this.class.term.prompt();
                }
            } else {
                // console.log(e.data, new TextEncoder().encode(e.data));
                this.class.shell_write(e.data.replace(/\n/g, "\r\n").replace(/\r\r\n/g, "\r\n"));
            }
        }
    }
    var shell_wss = new esp_ws();
    var ico = document.getElementById("ico");
    var svg = document.querySelectorAll("#ico svg")[0];
    var frame = window.parent.document.querySelectorAll("iframe")[0];
    if (frame) {
        var source_height = frame.style.height;
        ico.addEventListener("click", e => {
            let height = frame.style.height;
            if (height === "100%") {
                frame.style.height = source_height;
            } else
                frame.style.height = "100%";
            if (window.innerHeight == window.parent.innerHeight)
                svg.style = "transform: rotate(0deg);"
            else
                svg.style = "transform: rotate(180deg);"
        });
        if (window.innerHeight == window.parent.innerHeight)
            svg.style = "transform: rotate(0deg);"
        else
            svg.style = "transform: rotate(180deg);"
    } else
        ico.style.display = "none";
    document.addEventListener('paste', function (event) {
        var clipText = event.clipboardData.getData('Text');
        console.log(clipText);
    });
}